﻿using Newtonsoft.Json;
using WoodAdmin.Common.Helper;
using WoodAdmin.Common.Helper.Log;
using SqlSugar;
using System;
using System.Collections.Generic;
using System.Linq;
public class DbContext
{
    /// <summary>
    /// 数据库链接字符串
    /// </summary>
    private static string ConnectionString = ConfigurationUtil.DBConnectionString;

    /// <summary>
    /// 获取ORM数据库连接对象(只操作数据库一次的使用, 否则会进行多次数据库连接和关闭)
    /// 默认超时时间为30秒
    /// 默认为SQL Server数据库
    /// 默认自动关闭数据库链接, 多次操作数据库请勿使用该属性, 可能会造成性能问题
    /// 要自定义请使用GetIntance()方法或者直接使用Exec方法, 传委托
    /// </summary>
    public static SqlSugarClient Db 
    {
        get
        {
            return InitDB(30, ConfigurationUtil.DbType);
        }
    }

    /// <summary>
    /// 初始化ORM连接对象
    /// </summary>
    /// <param name="commandTimeOut">等待超时时间, 默认为30秒 (单位: 秒)</param>
    /// <param name="dbType">数据库类型</param>
    /// <param name="isAutoCloseConnection">是否自动关闭数据库连接, 默认不是, 如果设置为true, 则会在每次操作完数据库后, 即时关闭, 如果一个方法里面多次操作了数据库, 建议保持为false, 否则可能会引发性能问题</param>
    private static SqlSugarClient InitDB(int commandTimeOut = 30, DbType dbType = DbType.SqlServer, bool isAutoCloseConnection = true)
    {
        
        var db = new SqlSugarClient(new ConnectionConfig()
        {
            ConnectionString = ConnectionString,
            DbType = dbType,
            InitKeyType = InitKeyType.Attribute,//使用特性识别主键
            IsAutoCloseConnection = isAutoCloseConnection
        });
        db.Ado.CommandTimeOut = commandTimeOut;

        #region 记录SQL日志
        ExecuteSqlLogHandler _executeSqlLog = null;
        db.Aop.OnLogExecuting = (sql, pars) => //SQL执行前事件
        {
            //SQL控制台打印
            Console.WriteLine(sql + "\r\n" +
                db.Utilities.SerializeObject(pars.ToDictionary(it => it.ParameterName, it => it.Value)));
            Console.WriteLine();

            string par = string.Empty;
            if (pars.Length > 0)
            {
                Dictionary<string, object> dic = pars.ToDictionary(k => k.ParameterName, v => v.Value);
                par = JsonConvert.SerializeObject(dic).Replace(":", "=");
            }
            _executeSqlLog = new ExecuteSqlLogHandler(sql, par);
        };
        db.Aop.OnLogExecuted = (sql, pars) => //SQL执行完事件
        {
            _executeSqlLog.WriteLog();
        };

        db.Aop.OnError = (exp) =>//执行SQL 错误事件
        {
            _executeSqlLog.LogInfo.IsFail = 1;
            _executeSqlLog.LogInfo.Massage = exp.Message;
            _executeSqlLog.WriteLog();
        };
        #endregion

        return db;
    }

    /// <summary>
    /// 获得SqlSugarClient(使用该方法, 默认请手动释放资源, 如using(var db = SugarBase.GetIntance()){你的代码}, 如果把isAutoCloseConnection参数设置为true, 则无需手动释放, 会每次操作数据库释放一次, 可能会影响性能, 请自行判断使用)
    /// </summary>
    /// <param name="commandTimeOut">等待超时时间, 默认为30秒 (单位: 秒)</param>
    /// <param name="dbType">数据库类型, 默认为SQL Server</param>
    /// <param name="isAutoCloseConnection">是否自动关闭数据库连接, 默认不是, 如果设置为true, 则会在每次操作完数据库后, 即时关闭, 如果一个方法里面多次操作了数据库, 建议保持为false, 否则可能会引发性能问题</param>
    /// <returns></returns>
    public static SqlSugarClient GetIntance(int commandTimeOut = 30, DbType dbType = DbType.SqlServer, bool isAutoCloseConnection = true)
    {
        return InitDB(commandTimeOut, dbType, isAutoCloseConnection);
    }
}


